package com.functest.jpwise.deprecated.example;

import com.functest.jpwise.deprecated.example.fictionalwebsite.ECommerceWebSite;
import com.functest.jpwise.deprecated.example.fictionalwebsite.User;
import com.functest.jpwise.deprecated.example.fictionalwebsite.order.payment.*;

import com.functest.jpwise.deprecated.example.fictionalwebsite.order.Coupon;
import com.functest.jpwise.deprecated.example.fictionalwebsite.order.Order;
import com.functest.jpwise.deprecated.example.fictionalwebsite.order.Product;


import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.Parameterized;

/** Represents an example of a parameterized test.
 * This example verifies that a user can place an order through an E-commerce web-site. */
@RunWith(Parameterized.class) // This annotation tells JUnit to run this as a parameterized test.
public abstract class ExampleTest {
	private static int testCaseIndex = 0; // a counter to enumerate the test-cases for logging
	
	// === TEST PARAMETERS ===
	private User user; private Coupon coupon; private Product product; private Payment payment;
	
	/** Constructs a test case to verify that a user can place an order. */
	public ExampleTest(User user, Product product, Coupon coupon, Payment payment) {
		this.user = user; this.product = product; this.coupon = coupon; this.payment = payment;
	}

	/** Returns the recommended values to test for each test parameter.
	 * @return an array of arrays, where each sub-array contains values for one of the test parameters. */
	protected static Object[][] valuesToTestForEachParameter() {
		return new Object[][] {
			new User[] { User.REGISTERED_USER, User.UNREGISTERED_USER },
			new Product[] { Product.TYPICAL, Product.DROP_SHIP, Product.E_BOOK, Product.GIFT_CERTIFICATE },
			new Coupon[] { Coupon.FIVE_DOLLARS_OFF, Coupon.TEN_PERCENT_OFF, null },
			new Payment[] {
				new WireTransferPayment(), new CreditCardPayment(),
				new PayPalPayment(), new GiftCertificatePayment()
			}
		};
	}

	// === THE TEST ===
	/** Runs the test case. */
	@Test public void userCanPurchaseProductWithCouponAndPayment() {
		System.out.printf(
			"%nTest-case %d: user=«%s», product=«%s», coupon=«%s», payment=«%s»%n",
                testCaseIndex, user, product, coupon, payment
		);
        testCaseIndex++;

        System.out.println("Preparatory step: Construct an order.");
		final Order order = new Order();
		order.setUser(user);
		order.addProduct(product);
		order.setCoupon(coupon);
		order.addPayment(payment);

		System.out.println("Test step: Place the order.");
		final ECommerceWebSite webSite = new ECommerceWebSite();
		webSite.placeOrder(order);
	}
}
